import { AuthService } from './auth.service';
import { Injectable } from '@angular/core';
import { ActivatedRouteSnapshot, CanActivate, CanActivateChild, CanLoad, NavigationExtras, Router, RouterStateSnapshot, UrlTree, Route } from '@angular/router';
import { Observable, of } from 'rxjs';
/**
 * 调用身份服务来进行身份守卫
 *
 * @export
 * @class AuthGuard
 * @implements {CanActivate}
 */
@Injectable({
  providedIn: 'root'
})

export class AuthGuard implements CanActivate,CanActivateChild,CanLoad {

  constructor(private authService: AuthService,private router: Router){

  }

  /**
   * 1.对未登录的用户进行守卫，canActivate提供给一些url等路由信息
   * 但是关键怎么守卫的，还得另外写个函数
   * 2.这两个返回值 一个是boolean用来需要返回true来跳转，否则返回另一种UrlTree将
   * 准备跳转的URL替换成新的，也就是重定向了，这里不用navigate是因为 我已经在跳转的路上了，
   * 而navigate是重新开始一个跳转
   */
  canActivate(
    route: ActivatedRouteSnapshot,
    state: RouterStateSnapshot): Observable<boolean | UrlTree> | Promise<boolean | UrlTree> | boolean | UrlTree {
    // console.log('AuthGuard canActivated called')
    const url = state.url;
    return this.checkLogin(url);
  }

  canActivateChild(
    route: ActivatedRouteSnapshot,
    state: RouterStateSnapshot): Observable<boolean | UrlTree> | Promise<boolean | UrlTree> | boolean | UrlTree {
    // console.log('AuthGuard canActivated called')
    return this.canActivate(route,state);
  }


  checkLogin(url: string): Observable<boolean | UrlTree> | Promise<boolean | UrlTree> | boolean | UrlTree {
     if(this.authService.isLoginedIn)  return true

     /**
      * 如果没有登录则保存准备重定向的地址，等转到登陆页面登陆好了再跳转
      * 返回值类型是个UrlTree，因此要用router.parseUrl
      */
     this.authService.redirecturl = url;


     /**
      * 在路由中传递一个sessionId供全局使用
      */
     const sessionId = 123456789

     const navigatationExtras: NavigationExtras = {
         queryParams: { session_id: sessionId},
         fragment: 'anchor'
     }

     return this.router.createUrlTree(['/login'], navigatationExtras)

  }

  /**
   * 对未授权特性区加载的保护：只有已登录且访问管理特性区时才会加载admin.module一次
   */
  canLoad(route: Route): Observable<boolean | UrlTree> | Promise<boolean | UrlTree> | boolean | UrlTree {
      const url = `/${route.path}`
      return this.checkLogin(url)
  }

}
